package buildings;

import game.City;
import game.Costs;
import game.Earning;
import units.AbstractUnit;

public abstract class AbstractBuilding
{
	
	private boolean active = true;
	private boolean builded = false;
	private int level = 0;
	private int healthpoints = 500;
	private int defense = 1;
	private int rue = 0; //rue = rounds until earn
	private Earning earn = null;
	private Costs costs = null;
	
	private int buildCountdown = 0;	
	private int lastFullBuildCountdown = 0;
	
	abstract int getDefenseBonus();
	abstract int getHealthpointsBonus();
	abstract int getIncomeBonus();

	
	
	public boolean isActive() {
		return active;
	}
	public void setActive(boolean active) {
		this.active = active;
	}
	public int getBuildCountdown() {
		return buildCountdown;
	}
	public void setBuildCountdown(int buildCountdown) {
		this.buildCountdown = buildCountdown;
	}
	public int getLastFullBuildCountdown() {
		return lastFullBuildCountdown;
	}
	public void setLastFullBuildCountdown(int lastFullBuildCountdown) {
		this.lastFullBuildCountdown = lastFullBuildCountdown;
	}
	public int getHealthpoints() {
		return healthpoints;
	}
	public void setHealthpoints(int healthpoints) {
		this.healthpoints = healthpoints;
	}
	
	AbstractBuilding(int healthpoints, int defense)
	{
		this.healthpoints = healthpoints + this.getHealthpointsBonus();
		this.defense = defense;
	}
	
	public void builded() {
		builded = true;
		level = 1;
	}
	
	public void destroy() {
		builded = false;
	}
	
	public boolean isBuilded() {
		return builded;
	}
	
	public int getRue() {
		return rue;
	}
	public void setRue(int rue) {
		this.rue = rue;
	}
	public int getDefense() {
		return defense;
	}
	public void setDefense(int defense) {
		this.defense = defense;
	}
	public int getLevel() {
		return level;
	}
	public void setLevel(int level) {
		this.level = level;
	}
	public Earning getEarn() {
		return earn;
	}
	public void setEarn(Earning earn) {
		this.earn = earn;
	}
	public Costs getCosts() {
		return costs;
	}
	public void setCosts(Costs costs) {
		this.costs = costs;
	}
	
	public void checkEarning(City city) {
		if (earn==null) return;
		if (!active) return;
		if (!builded) return;
		rue = rue - 1;
		if (rue <= 0) {
			earn(city);
			rue = earn.getRepeatRound();
		}
	}
	
	private void earn(City city) {
		for (int i = 0; i<5;i++) {
			city.earn(i, this.earn.getWare(this.level,i));
		}		
	}
	
	public void levelup() {
		this.level = this.level + 1;
	}
	
	
	int hurt(int damage) {
		if (!builded) return 0;
		if (healthpoints < damage) {
			int lostHealthpoints = healthpoints;
			healthpoints = 0;
			return lostHealthpoints;
		}
		healthpoints = healthpoints - damage;
		return damage;
	}
	public void paySupply(City city) {
		if (!active) return;
		if (!builded) return;
		if (!city.canAffordSupply(this)) {
			setActive(false);
			return;
		}
		for (int i = 0; i<5;i++) {
			city.pay(i, this.costs.getSupply(this.level,i));
		}	
	}
	
	public String getName() {
		return this.getClass().getSimpleName();
	}
	
	public static AbstractBuilding findBuildingByName(String name) {
		name = name.toLowerCase();
		if (name.equals("farm")) {
			return(new Farm());
		} else if (name.equals("lumberjack")) {
			return(new Lumberjack());
		} else if (name.equals("quarry")) {
			return(new Quarry());
		} else if (name.equals("ore mine")) {
			return(new Ore_Mine());
		} else if (name.equals("residential area")) {
			return(new Residential_Area());
		} else if (name.equals("defence wall")) {
			return(null);
		}
		return null;
	}
	
	public String getBuildPercent() {
		return ((lastFullBuildCountdown - buildCountdown )*100/lastFullBuildCountdown) + "%";
	}
}